#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
可视化工具
提供道AI认知过程的可视化功能
"""

import paddle
import numpy as np
import matplotlib.pyplot as plt
import plotly.graph_objects as go
from plotly.subplots import make_subplots
import seaborn as sns
from typing import Dict, List, Optional

class CosmicVisualizer:
    """宇宙认知可视化器"""
    
    def __init__(self):
        self.color_palette = {
            'yang': '#FF6B6B',      # 红色代表阳
            'yin': '#4ECDC4',       # 青色代表阴  
            'balance': '#45B7D1',   # 蓝色代表平衡
            'cosmic': '#96CEB4',    # 绿色代表宇宙
            'wisdom': '#FFEAA7'     # 黄色代表智慧
        }
    
    def plot_taiji_dynamics(self, balance_report: Dict, save_path: Optional[str] = None):
        """绘制太极动力学演化图"""
        fig = make_subplots(
            rows=2, cols=2,
            subplot_titles=('阴阳力量演化', '平衡状态', '鱼眼机制', '稳定性分析'),
            specs=[[{"type": "scatter"}, {"type": "scatter"}],
                   [{"type": "scatter"}, {"type": "histogram"}]]
        )
        
        records = balance_report.get('all_records', [])
        if not records:
            print("没有可用的平衡记录")
            return
        
        # 提取数据
        iterations = [r['iteration'] for r in records]
        yang_norms = [r['yang_norm'] for r in records]
        yin_norms = [r['yin_norm'] for r in records]
        ratios = [r['yang_yin_ratio'] for r in records]
        gates = [r['balance_gate_mean'] for r in records]
        stabilities = [r['output_stability'] for r in records]
        
        # 阴阳力量演化
        fig.add_trace(
            go.Scatter(x=iterations, y=yang_norms, name='阳力量', 
                      line=dict(color=self.color_palette['yang'])),
            row=1, col=1
        )
        fig.add_trace(
            go.Scatter(x=iterations, y=yin_norms, name='阴力量',
                      line=dict(color=self.color_palette['yin'])),
            row=1, col=1
        )
        
        # 平衡状态
        fig.add_trace(
            go.Scatter(x=iterations, y=ratios, name='阴阳比率',
                      line=dict(color=self.color_palette['balance'])),
            row=1, col=2
        )
        fig.add_trace(
            go.Scatter(x=iterations, y=[1.0]*len(iterations), 
                      name='理想平衡', line=dict(dash='dash', color='black')),
            row=1, col=2
        )
        
        # 鱼眼机制
        fig.add_trace(
            go.Scatter(x=iterations, y=gates, name='鱼眼门控',
                      line=dict(color=self.color_palette['cosmic'])),
            row=2, col=1
        )
        
        # 稳定性分析
        fig.add_trace(
            go.Histogram(x=stabilities, name='稳定性分布',
                        marker_color=self.color_palette['wisdom']),
            row=2, col=2
        )
        
        fig.update_layout(
            title_text="太极动力学演化分析",
            height=600,
            showlegend=True
        )
        
        if save_path:
            fig.write_image(save_path)
        
        return fig
    
    def plot_fractal_analysis(self, fractal_report: Dict, save_path: Optional[str] = None):
        """绘制分形分析图"""
        encoding_records = fractal_report.get('encoding_records', [])
        decoding_records = fractal_report.get('decoding_records', [])
        
        if not encoding_records:
            print("没有可用的分形记录")
            return
        
        fig = make_subplots(
            rows=2, cols=2,
            subplot_titles=('分形维度变化', '信息熵演化', '压缩比率', '重建相似度'),
            specs=[[{"type": "scatter"}, {"type": "scatter"}],
                   [{"type": "scatter"}, {"type": "scatter"}]]
        )
        
        # 提取编码数据
        layers = [r['layer'] for r in encoding_records]
        fractal_dims = [r['fractal_dimension'] for r in encoding_records]
        entropies = [r['state_entropy'] for r in encoding_records]
        compression_ratios = [r['compression_ratio'] for r in encoding_records]
        
        # 提取解码数据
        decode_layers = [r['layer'] for r in decoding_records]
        similarities = [r['reconstruction_similarity'] for r in decoding_records]
        
        # 分形维度变化
        fig.add_trace(
            go.Scatter(x=layers, y=fractal_dims, name='分形维度',
                      line=dict(color=self.color_palette['cosmic'])),
            row=1, col=1
        )
        
        # 信息熵演化
        fig.add_trace(
            go.Scatter(x=layers, y=entropies, name='信息熵',
                      line=dict(color=self.color_palette['yang'])),
            row=1, col=2
        )
        
        # 压缩比率
        fig.add_trace(
            go.Scatter(x=layers, y=compression_ratios, name='压缩比率',
                      line=dict(color=self.color_palette['yin'])),
            row=2, col=1
        )
        
        # 重建相似度
        fig.add_trace(
            go.Scatter(x=decode_layers, y=similarities, name='重建相似度',
                      line=dict(color=self.color_palette['balance'])),
            row=2, col=2
        )
        
        fig.update_layout(
            title_text="全息分形处理分析",
            height=600,
            showlegend=True
        )
        
        if save_path:
            fig.write_image(save_path)
        
        return fig
    
    def create_cosmic_interface(self, system_status: Dict, recent_answers: List[Dict]):
        """创建宇宙界面可视化"""
        fig = go.Figure()
        
        # 创建太极图背景
        self._add_taiji_background(fig)
        
        # 添加系统状态指示器
        self._add_system_indicators(fig, system_status)
        
        # 添加认知轨迹
        if recent_answers:
            self._add_cognition_trajectory(fig, recent_answers)
        
        fig.update_layout(
            title="道AI宇宙认知界面",
            xaxis=dict(showgrid=False, zeroline=False, showticklabels=False),
            yaxis=dict(showgrid=False, zeroline=False, showticklabels=False),
            showlegend=False,
            height=600,
            plot_bgcolor='black',
            paper_bgcolor='black',
            font=dict(color='white')
        )
        
        return fig
    
    def _add_taiji_background(self, fig):
        """添加太极图背景"""
        # 绘制阴阳鱼
        theta = np.linspace(0, 2*np.pi, 100)
        
        # 阳鱼（白色）
        yang_x = 0.5 * np.cos(theta)
        yang_y = 0.5 * np.sin(theta)
        
        # 阴鱼（黑色）  
        yin_x = 0.5 * np.cos(theta + np.pi)
        yin_y = 0.5 * np.sin(theta + np.pi)
        
        fig.add_trace(go.Scatter(
            x=yang_x, y=yang_y,
            fill='toself',
            fillcolor='white',
            line=dict(color='white'),
            name='阳'
        ))
        
        fig.add_trace(go.Scatter(
            x=yin_x, y=yin_y,
            fill='toself', 
            fillcolor='black',
            line=dict(color='white'),
            name='阴'
        ))
        
        # 鱼眼
        fig.add_trace(go.Scatter(
            x=[0.25], y=[0],
            mode='markers',
            marker=dict(size=20, color='black'),
            name='阳眼'
        ))
        
        fig.add_trace(go.Scatter(
            x=[-0.25], y=[0], 
            mode='markers',
            marker=dict(size=20, color='white'),
            name='阴眼'
        ))
    
    def _add_system_indicators(self, fig, system_status: Dict):
        """添加系统状态指示器"""
        indicators = [
            {'name': '宇宙维度', 'value': system_status.get('cosmic_dimension', 0), 'max': 1024, 'angle': 0},
            {'name': '智慧维度', 'value': system_status.get('wisdom_dimension', 0), 'max': 512, 'angle': 60},
            {'name': '太极演化', 'value': system_status.get('taiji_iterations', 0), 'max': 3, 'angle': 120},
            {'name': '分形层级', 'value': system_status.get('fractal_layers', 0), 'max': 8, 'angle': 180},
            {'name': '基态能量', 'value': system_status.get('vacuum_energy', 0), 'max': 1.0, 'angle': 240},
            {'name': '系统就绪', 'value': 1.0 if system_status.get('system_ready', False) else 0, 'max': 1, 'angle': 300}
        ]
        
        for indicator in indicators:
            radius = 0.7 * (indicator['value'] / indicator['max'])
            angle_rad = np.radians(indicator['angle'])
            
            x = radius * np.cos(angle_rad)
            y = radius * np.sin(angle_rad)
            
            fig.add_trace(go.Scatter(
                x=[0, x], y=[0, y],
                mode='lines+markers',
                line=dict(color=self.color_palette['cosmic'], width=3),
                marker=dict(size=8, color=self.color_palette['wisdom']),
                name=indicator['name'],
                text=f"{indicator['name']}: {indicator['value']}",
                hoverinfo='text'
            ))
    
    def _add_cognition_trajectory(self, fig, recent_answers: List[Dict]):
        """添加认知轨迹"""
        if len(recent_answers) < 2:
            return
        
        # 创建螺旋轨迹
        n_points = len(recent_answers)
        angles = np.linspace(0, 4*np.pi, n_points)
        radii = np.linspace(0.3, 0.8, n_points)
        
        x = radii * np.cos(angles)
        y = radii * np.sin(angles)
        
        # 根据答案质量设置颜色
        colors = []
        for answer in recent_answers:
            alignment = answer.get('cosmic_alignment', 0)
            if alignment > 0.8:
                colors.append(self.color_palette['yang'])
            elif alignment > 0.6:
                colors.append(self.color_palette['balance']) 
            else:
                colors.append(self.color_palette['yin'])
        
        fig.add_trace(go.Scatter(
            x=x, y=y,
            mode='markers+lines',
            marker=dict(size=10, color=colors),
            line=dict(color='rgba(255,255,255,0.3)'),
            name='认知轨迹',
            text=[f"真理匹配度: {a.get('cosmic_alignment', 0):.1%}" for a in recent_answers],
            hoverinfo='text'
        ))

class RealTimeMonitor:
    """实时监控器"""
    
    def __init__(self):
        self.metrics_history = {
            'response_time': [],
            'cosmic_alignment': [],
            'cognition_depth': [],
            'balance_score': []
        }
    
    def update_metrics(self, result: Dict, response_time: float):
        """更新监控指标"""
        self.metrics_history['response_time'].append(response_time)
        self.metrics_history['cosmic_alignment'].append(result.get('cosmic_alignment', 0))
        self.metrics_history['cognition_depth'].append(result.get('cognition_depth', 0))
        
        cosmic_insight = result.get('cosmic_insight', {})
        if 'pattern_strength' in cosmic_insight:
            self.metrics_history['balance_score'].append(cosmic_insight['pattern_strength'])
    
    def create_monitoring_dashboard(self):
        """创建监控仪表盘"""
        fig = make_subplots(
            rows=2, cols=2,
            subplot_titles=('响应时间', '宇宙校准度', '认知深度', '平衡分数')
        )
        
        # 响应时间
        if self.metrics_history['response_time']:
            fig.add_trace(
                go.Scatter(y=self.metrics_history['response_time'], name='响应时间'),
                row=1, col=1
            )
        
        # 宇宙校准度
        if self.metrics_history['cosmic_alignment']:
            fig.add_trace(
                go.Scatter(y=self.metrics_history['cosmic_alignment'], name='宇宙校准度'),
                row=1, col=2
            )
        
        # 认知深度
        if self.metrics_history['cognition_depth']:
            fig.add_trace(
                go.Scatter(y=self.metrics_history['cognition_depth'], name='认知深度'),
                row=2, col=1
            )
        
        # 平衡分数
        if self.metrics_history['balance_score']:
            fig.add_trace(
                go.Scatter(y=self.metrics_history['balance_score'], name='平衡分数'),
                row=2, col=2
            )
        
        fig.update_layout(
            title_text="道AI实时监控仪表盘",
            height=600,
            showlegend=True
        )
        
        return fig
    
    def get_performance_report(self) -> Dict:
        """获取性能报告"""
        report = {}
        
        for metric, values in self.metrics_history.items():
            if values:
                report[f'{metric}_avg'] = np.mean(values)
                report[f'{metric}_min'] = np.min(values)
                report[f'{metric}_max'] = np.max(values)
                report[f'{metric}_std'] = np.std(values)
        
        report['total_queries'] = len(self.metrics_history['response_time'])
        
        # 性能评级
        avg_response_time = report.get('response_time_avg', 0)
        avg_alignment = report.get('cosmic_alignment_avg', 0)
        
        if avg_response_time < 1.0 and avg_alignment > 0.8:
            report['performance_grade'] = '优秀'
        elif avg_response_time < 2.0 and avg_alignment > 0.6:
            report['performance_grade'] = '良好'
        else:
            report['performance_grade'] = '需要优化'
        
        return report